#include "../../inc/local/MyTask.h"

#include <json/json.h>
#include <algorithm>
#include <iostream>
#include <string>
#include <queue>
#include <vector>


using std::priority_queue;
using std::string;
using std::vector;

namespace SC
{
    MyTask::MyTask(const string &queryWord, const TcpConnectionPtr &ptr)
    : _queryWord(queryWord), _ptr(ptr), _priQueue()
    {
    }

    void MyTask::execute()
    {
        CachePtr cache = CacheManager::getpInstance()->getCacheMap()[pthread_self()];

        int frequency = cache->get(_queryWord);
        if(-1 == frequency)
            cache->put(_queryWord, 1);
        else 
        {
            MyResult res(_queryWord, frequency, 0);
            cache->put(_queryWord, frequency+1);
        }

        MyDict::getpInstance()->query(_queryWord, _priQueue);

        while(_priQueue.size() > (std::stoul(Configuration::getpInstance()->getConfigMap()["priQueue_size"])))
            _priQueue.pop();
        
        string msg = jsonPackage();
        _ptr->sendInLoop(msg);

        // test code
        // printf("---------------\n");
        // while (!_priQueue.empty())
        // {
        //     std::cout << _priQueue.top()._word << ": " << _priQueue.top()._frequency << std::endl;
        //     _priQueue.pop();
        // }
        
    }

    string MyTask::jsonPackage()
    {
        Json::Value arr;
        Json::Value root;
        Json::Value wordres;
        vector<MyResult> rvec;
        while (!_priQueue.empty())
        {
            MyResult res = _priQueue.top();
            rvec.push_back(res);
            _priQueue.pop();
        }

        for(auto it = rvec.rbegin(); it != rvec.rend(); it++)
        {
            MyResult res = *it;
            wordres["word"] = res._word;
            wordres["frequency"] = res._frequency;
            wordres["distance"] = res._distance;
            root.append(wordres);
        }

        arr["array"] = Json::Value(root);
        return arr.toStyledString();
    }
}